// Copyright 2021 ETH Zurich and University of Bologna.
// Solderpad Hardware License, Version 0.51, see LICENSE for details.
// SPDX-License-Identifier: SHL-0.51
//
// Author: Matteo Perotti <mperotti@iis.ee.ethz.ch>
//         Basile Bougenot <bbougenot@student.ethz.ch>

#include "float_macros.h"
#include "vector_macros.h"

// Simple random test with similar values + 1 subnormal
void TEST_CASE1(void) {
  VSET(16, e16, m1);
  //              -0.6377, -0.2332,  0.9458, -0.2612, -0.6772,  0.4543,  0.1002,
  //              0.7764,  0.7979, -0.8599,  0.7837, -0.2461,  0.4221,  0.2251,
  //              0.7739,  0.1461
  VLOAD_16(v2, 0xb91a, 0xb376, 0x3b91, 0xb42e, 0xb96b, 0x3745, 0x2e69, 0x3a36,
           0x3a62, 0xbae1, 0x3a45, 0xb3e0, 0x36c1, 0x3334, 0x3a31, 0x30ad);
  //               0.9551, -0.6787,  0.5605, -0.7305, -0.7197, -0.1581,  0.7271,
  //               0.6113,  0.2971, -0.8062,  0.9668, -0.5278,  0.3972, -0.1084,
  //               -0.3015,  0.9556
  VLOAD_16(v3, 0x3ba4, 0xb96e, 0x387c, 0xb9d8, 0xb9c2, 0xb10f, 0x39d1, 0x38e4,
           0x34c1, 0xba73, 0x3bbc, 0xb839, 0x365b, 0xaef0, 0xb4d3, 0x3ba5);
  //               0.7402,  0.0935,  0.1455, -0.2771,  0.3347,  0.7964,  0.6543,
  //               -0.7534,  0.2476,  0.0338,  0.9980,  0.3284,  0.2239,
  //               -0.4551,  0.6694, -0.8550
  VLOAD_16(v1, 0x39ec, 0x2dfc, 0x30a8, 0xb46f, 0x355b, 0x3a5f, 0x393c, 0xba07,
           0x33ec, 0x2853, 0x3bfc, 0x3541, 0x332a, 0xb748, 0x395b, 0xbad7);
  asm volatile("vfnmacc.vv v1, v2, v3");
  //              -0.1313, -0.2517, -0.6758,  0.0863, -0.8223, -0.7246, -0.7271,
  //              0.2788, -0.4846, -0.7271, -1.7559, -0.4583, -0.3916,  0.4795,
  //              -0.4360,  0.7153
  VCMP_U16(1, v1, 0xb033, 0xb407, 0xb968, 0x2d86, 0xba94, 0xb9cc, 0xb9d1,
           0x3476, 0xb7c1, 0xb9d1, 0xbf06, 0xb755, 0xb644, 0x37ac, 0xb6fa,
           0x39b9);

  VSET(16, e32, m1);
  //              -0.17374928, -0.36242354, -0.18093164,  0.94970566,
  //              -0.45790458, -0.17780401, -0.51985794, -0.04832974,
  //              0.13252106,  0.77533042,  0.42536697, -0.72199643,
  //              -0.25088808,  0.28798762,  0.66300607, -0.63549894
  VLOAD_32(v2, 0xbe31eb55, 0xbeb98f94, 0xbe394625, 0x3f731fe9, 0xbeea7278,
           0xbe361241, 0xbf051569, 0xbd45f569, 0x3e07b39a, 0x3f467c0e,
           0x3ed9c9b3, 0xbf38d4c2, 0xbe807467, 0x3e93731d, 0x3f29bac4,
           0xbf22b00f);
  //              -0.61242568,  0.71439523, -0.15632962,  0.10917858,
  //              0.19637996, -0.88467985,  0.73412597, -0.98048240, 0.25438991,
  //              -0.02058743, -0.00876777,  0.21936898, -0.71130067,
  //              -0.29675287, -0.96093589,  0.24695934
  VLOAD_32(v3, 0xbf1cc7ee, 0x3f36e29b, 0xbe2014df, 0x3ddf9905, 0x3e4917d4,
           0xbf627a61, 0x3f3befae, 0xbf7b00e5, 0x3e823f65, 0xbca8a6f9,
           0xbc0fa6af, 0x3e60a243, 0xbf3617cd, 0xbe97effe, 0xbf75ffe5,
           0x3e7ce2e9);
  //               0.77600455,  0.02542816, -0.63618338,  0.11704731,
  //               0.45613721, -0.90825689,  0.21235447,  0.35766414,
  //               0.08650716, -0.98431164,  0.21029140, -0.92919809,
  //               0.46440944,  0.70648551, -0.80876821, -0.19595607
  VLOAD_32(v1, 0x3f46a83c, 0x3cd04eb8, 0xbf22dcea, 0x3defb680, 0x3ee98ad1,
           0xbf688386, 0x3e597373, 0x3eb71fc1, 0x3db12aaa, 0xbf7bfbd9,
           0x3e5756a1, 0xbf6ddfed, 0x3eedc713, 0x3f34dc3c, 0xbf4f0b6f,
           0xbe48a8b5);
  asm volatile("vfnmacc.vv v1, v2, v3");
  //              -0.88241309,  0.23348548,  0.60789841, -0.22073483,
  //              -0.36621392,  0.75095725,  0.16928674, -0.40505061,
  //              -0.12021918,  1.00027370, -0.20656188,  1.08758175,
  //              -0.64286631, -0.62102437,  1.44587445,  0.35289848
  VCMP_U32(2, v1, 0xbf61e5d3, 0x3e6f16d2, 0x3f1b9f3b, 0xbe62084f, 0xbebb8064,
           0x3f403ebc, 0x3e2d5982, 0xbecf62cb, 0xbdf63579, 0x3f8008f8,
           0xbe5384f5, 0x3f8b35e1, 0xbf2492e3, 0xbf1efb74, 0x3fb9126b,
           0x3eb4af1c);

  VSET(16, e64, m1);
  //              -0.3252450595073633,  0.4758165631309326, -0.1595578232245429,
  //              -0.5062008461482019, -0.8497827573746595, -0.1941654045426651,
  //              0.5653121187716577, -0.9852357785633095, -0.4238236947700038,
  //              0.5852522737985073,  0.4009389814391957, -0.8725649196362917,
  //              -0.5946782335830663,  0.4175703122760628, -0.6355596052793091,
  //              -0.3469340725892474
  VLOAD_64(v2, 0xbfd4d0d0a77142c0, 0x3fde73c75062b7e8, 0xbfc46c6408490198,
           0xbfe032cc1ded3ff0, 0xbfeb316b9bf41faa, 0xbfc8da6977433ee0,
           0x3fe2170970c503fe, 0xbfef870d2ef8e992, 0xbfdb1fed6b13a6c0,
           0x3fe2ba62f9fbf9aa, 0x3fd9a8fbf93e43f0, 0xbfebec0d442f3114,
           0xbfe3079aa59c3bf4, 0x3fdab978d4c06588, 0xbfe4568118eaaa68,
           0xbfd6342af7e8e3dc);
  //               0.9024789401717532,  0.1750129013440402,  0.5031110880652467,
  //               -0.2303324647743561, -0.3880673069078899,
  //               -0.9441232974464955, -0.9718449040015202, 0.6713775626400460,
  //               -0.0912048565692380, -0.5347347522064834,
  //               -0.5209348837668262,  0.1676058792979986,
  //               -0.3611782231841894,  0.5839305722445856,
  //               -0.5690013462620132, -0.7273345685963009
  VLOAD_64(v3, 0x3fece11b83abb9b8, 0x3fc666d29fd34b08, 0x3fe0197c6cafd8c4,
           0xbfcd7b88c1b4daf0, 0xbfd8d61841f43c54, 0xbfee36420fbd9482,
           0xbfef195a7bef10b4, 0x3fe57beccc59d47e, 0xbfb7593394338500,
           0xbfe11c8c0e185e4a, 0xbfe0ab7fa223f876, 0x3fc5741c0519e298,
           0xbfd71d8b44269f74, 0x3fe2af8f2add9a18, 0xbfe235424fb26902,
           0xbfe74653252be25a);
  //              -0.0769255470598902, -0.8447241112550155, -0.1913688167412757,
  //              0.7663381230505260,  0.2058488268749510, -0.0251549939511286,
  //              0.5275264461714482, -0.7602756587514194,  0.6498044022974587,
  //              -0.7128277097157256, -0.8385947434294139,  0.8834902787005550,
  //              0.5936682304042178,  0.1532178226844403, -0.5096194622607613,
  //              -0.8578075287458693
  VLOAD_64(v1, 0xbfb3b16484d96110, 0xbfeb07fadbff7462, 0xbfc87ec5fcb06230,
           0x3fe885d78705c2d4, 0x3fca59411dac8758, 0xbf99c23b11679a80,
           0x3fe0e17f24429b70, 0xbfe8542d9e4907ce, 0x3fe4cb329a1542de,
           0xbfe6cf7c0e9d2c04, 0xbfead5c4a4b40f1a, 0x3fec458d67ab4a36,
           0x3fe2ff5484485472, 0x3fc39ca440cc0820, 0xbfe04ecd797a151a,
           0xbfeb7328c6473c1e);
  asm volatile("vfnmacc.vv v1, v2, v3");
  //               0.3704523636601942,  0.7614500740339213,  0.2716441267930978,
  //               -0.8829326116147059, -0.5356217329860959,
  //               -0.1581610880357251, 0.0218692556270895,  1.4217408543890222,
  //               -0.6884591815896014,  1.0257824393236514,  1.0474578451230310,
  //               -0.7372432681003268, -0.8084530581760619,
  //               -0.3970498940841519,  0.1479851912270807,  0.6054703847278113
  VCMP_U64(3, v1, 0x3fd7b57dd4a95f28, 0x3fe85dcc8bb06629, 0x3fd1629e0c2e846c,
           0xbfec40fbe46ea001, 0xbfe123d0304677d2, 0xbfc43e9f5e4e7ddd,
           0x3f9664e4e6d32991, 0x3ff6bf73568fcea3, 0xbfe607db8cb1dd4b,
           0x3ff0699ad8db4c8b, 0x3ff0c263284bdf71, 0xbfe7977f31b5fc6d,
           0xbfe9ded8f2a6f4b5, 0xbfd96943f57e3046, 0x3fc2f12dc24e6a42,
           0x3fe360036da34794);
};

// Simple random test with similar values + 1 subnormal (masked)
// The numbers are the same of TEST_CASE1
void TEST_CASE2(void) {
  VSET(16, e16, m1);
  //              -0.6377, -0.2332,  0.9458, -0.2612, -0.6772,  0.4543,  0.1002,
  //              0.7764,  0.7979, -0.8599,  0.7837, -0.2461,  0.4221,  0.2251,
  //              0.7739,  0.1461
  VLOAD_16(v2, 0xb91a, 0xb376, 0x3b91, 0xb42e, 0xb96b, 0x3745, 0x2e69, 0x3a36,
           0x3a62, 0xbae1, 0x3a45, 0xb3e0, 0x36c1, 0x3334, 0x3a31, 0x30ad);
  //               0.9551, -0.6787,  0.5605, -0.7305, -0.7197, -0.1581,  0.7271,
  //               0.6113,  0.2971, -0.8062,  0.9668, -0.5278,  0.3972, -0.1084,
  //               -0.3015,  0.9556
  VLOAD_16(v3, 0x3ba4, 0xb96e, 0x387c, 0xb9d8, 0xb9c2, 0xb10f, 0x39d1, 0x38e4,
           0x34c1, 0xba73, 0x3bbc, 0xb839, 0x365b, 0xaef0, 0xb4d3, 0x3ba5);
  VLOAD_8(v0, 0xAA, 0xAA);
  //               0.7402,  0.0935,  0.1455, -0.2771,  0.3347,  0.7964,  0.6543,
  //               -0.7534,  0.2476,  0.0338,  0.9980,  0.3284,  0.2239,
  //               -0.4551,  0.6694, -0.8550
  VLOAD_16(v1, 0x39ec, 0x2dfc, 0x30a8, 0xb46f, 0x355b, 0x3a5f, 0x393c, 0xba07,
           0x33ec, 0x2853, 0x3bfc, 0x3541, 0x332a, 0xb748, 0x395b, 0xbad7);
  asm volatile("vfnmacc.vv v1, v2, v3, v0.t");
  //               0.0000, -0.2517,  0.0000,  0.0863,  0.0000, -0.7246,  0.0000,
  //               0.2788,  0.0000, -0.7271,  0.0000, -0.4583,  0.0000,  0.4795,
  //               0.0000,  0.7153
  VCMP_U16(4, v1, 0x39ec, 0xb407, 0x30a8, 0x2d86, 0x355b, 0xb9cc, 0x393c,
           0x3476, 0x33ec, 0xb9d1, 0x3bfc, 0xb755, 0x332a, 0x37ac, 0x395b,
           0x39b9);

  VSET(16, e32, m1);
  //              -0.17374928, -0.36242354, -0.18093164,  0.94970566,
  //              -0.45790458, -0.17780401, -0.51985794, -0.04832974,
  //              0.13252106,  0.77533042,  0.42536697, -0.72199643,
  //              -0.25088808,  0.28798762,  0.66300607, -0.63549894
  VLOAD_32(v2, 0xbe31eb55, 0xbeb98f94, 0xbe394625, 0x3f731fe9, 0xbeea7278,
           0xbe361241, 0xbf051569, 0xbd45f569, 0x3e07b39a, 0x3f467c0e,
           0x3ed9c9b3, 0xbf38d4c2, 0xbe807467, 0x3e93731d, 0x3f29bac4,
           0xbf22b00f);
  //              -0.61242568,  0.71439523, -0.15632962,  0.10917858,
  //              0.19637996, -0.88467985,  0.73412597, -0.98048240, 0.25438991,
  //              -0.02058743, -0.00876777,  0.21936898, -0.71130067,
  //              -0.29675287, -0.96093589,  0.24695934
  VLOAD_32(v3, 0xbf1cc7ee, 0x3f36e29b, 0xbe2014df, 0x3ddf9905, 0x3e4917d4,
           0xbf627a61, 0x3f3befae, 0xbf7b00e5, 0x3e823f65, 0xbca8a6f9,
           0xbc0fa6af, 0x3e60a243, 0xbf3617cd, 0xbe97effe, 0xbf75ffe5,
           0x3e7ce2e9);
  VLOAD_8(v0, 0xAA, 0xAA);
  //               0.77600455,  0.02542816, -0.63618338,  0.11704731,
  //               0.45613721, -0.90825689,  0.21235447,  0.35766414,
  //               0.08650716, -0.98431164,  0.21029140, -0.92919809,
  //               0.46440944,  0.70648551, -0.80876821, -0.19595607
  VLOAD_32(v1, 0x3f46a83c, 0x3cd04eb8, 0xbf22dcea, 0x3defb680, 0x3ee98ad1,
           0xbf688386, 0x3e597373, 0x3eb71fc1, 0x3db12aaa, 0xbf7bfbd9,
           0x3e5756a1, 0xbf6ddfed, 0x3eedc713, 0x3f34dc3c, 0xbf4f0b6f,
           0xbe48a8b5);
  asm volatile("vfnmacc.vv v1, v2, v3, v0.t");
  //               0.00000000,  0.23348548,  0.00000000, -0.22073483,
  //               0.00000000,  0.75095725,  0.00000000, -0.40505061,
  //               0.00000000,  1.00027370,  0.00000000,  1.08758175,
  //               0.00000000, -0.62102437,  0.00000000,  0.35289848
  VCMP_U32(5, v1, 0x3f46a83c, 0x3e6f16d2, 0xbf22dcea, 0xbe62084f, 0x3ee98ad1,
           0x3f403ebc, 0x3e597373, 0xbecf62cb, 0x3db12aaa, 0x3f8008f8,
           0x3e5756a1, 0x3f8b35e1, 0x3eedc713, 0xbf1efb74, 0xbf4f0b6f,
           0x3eb4af1c);

  VSET(16, e64, m1);
  //              -0.3252450595073633,  0.4758165631309326, -0.1595578232245429,
  //              -0.5062008461482019, -0.8497827573746595, -0.1941654045426651,
  //              0.5653121187716577, -0.9852357785633095, -0.4238236947700038,
  //              0.5852522737985073,  0.4009389814391957, -0.8725649196362917,
  //              -0.5946782335830663,  0.4175703122760628, -0.6355596052793091,
  //              -0.3469340725892474
  VLOAD_64(v2, 0xbfd4d0d0a77142c0, 0x3fde73c75062b7e8, 0xbfc46c6408490198,
           0xbfe032cc1ded3ff0, 0xbfeb316b9bf41faa, 0xbfc8da6977433ee0,
           0x3fe2170970c503fe, 0xbfef870d2ef8e992, 0xbfdb1fed6b13a6c0,
           0x3fe2ba62f9fbf9aa, 0x3fd9a8fbf93e43f0, 0xbfebec0d442f3114,
           0xbfe3079aa59c3bf4, 0x3fdab978d4c06588, 0xbfe4568118eaaa68,
           0xbfd6342af7e8e3dc);
  //               0.9024789401717532,  0.1750129013440402,  0.5031110880652467,
  //               -0.2303324647743561, -0.3880673069078899,
  //               -0.9441232974464955, -0.9718449040015202, 0.6713775626400460,
  //               -0.0912048565692380, -0.5347347522064834,
  //               -0.5209348837668262,  0.1676058792979986,
  //               -0.3611782231841894,  0.5839305722445856,
  //               -0.5690013462620132, -0.7273345685963009
  VLOAD_64(v3, 0x3fece11b83abb9b8, 0x3fc666d29fd34b08, 0x3fe0197c6cafd8c4,
           0xbfcd7b88c1b4daf0, 0xbfd8d61841f43c54, 0xbfee36420fbd9482,
           0xbfef195a7bef10b4, 0x3fe57beccc59d47e, 0xbfb7593394338500,
           0xbfe11c8c0e185e4a, 0xbfe0ab7fa223f876, 0x3fc5741c0519e298,
           0xbfd71d8b44269f74, 0x3fe2af8f2add9a18, 0xbfe235424fb26902,
           0xbfe74653252be25a);
  VLOAD_8(v0, 0xAA, 0xAA);
  //              -0.0769255470598902, -0.8447241112550155, -0.1913688167412757,
  //              0.7663381230505260,  0.2058488268749510, -0.0251549939511286,
  //              0.5275264461714482, -0.7602756587514194,  0.6498044022974587,
  //              -0.7128277097157256, -0.8385947434294139,  0.8834902787005550,
  //              0.5936682304042178,  0.1532178226844403, -0.5096194622607613,
  //              -0.8578075287458693
  VLOAD_64(v1, 0xbfb3b16484d96110, 0xbfeb07fadbff7462, 0xbfc87ec5fcb06230,
           0x3fe885d78705c2d4, 0x3fca59411dac8758, 0xbf99c23b11679a80,
           0x3fe0e17f24429b70, 0xbfe8542d9e4907ce, 0x3fe4cb329a1542de,
           0xbfe6cf7c0e9d2c04, 0xbfead5c4a4b40f1a, 0x3fec458d67ab4a36,
           0x3fe2ff5484485472, 0x3fc39ca440cc0820, 0xbfe04ecd797a151a,
           0xbfeb7328c6473c1e);
  asm volatile("vfnmacc.vv v1, v2, v3, v0.t");
  //               0.0000000000000000,  0.7614500740339213,  0.0000000000000000,
  //               -0.8829326116147059,  0.0000000000000000,
  //               -0.1581610880357251, 0.0000000000000000,  1.4217408543890222,
  //               0.0000000000000000,  1.0257824393236514,  0.0000000000000000,
  //               -0.7372432681003268,  0.0000000000000000,
  //               -0.3970498940841519,  0.0000000000000000,  0.6054703847278113
  VCMP_U64(6, v1, 0xbfb3b16484d96110, 0x3fe85dcc8bb06629, 0xbfc87ec5fcb06230,
           0xbfec40fbe46ea001, 0x3fca59411dac8758, 0xbfc43e9f5e4e7ddd,
           0x3fe0e17f24429b70, 0x3ff6bf73568fcea3, 0x3fe4cb329a1542de,
           0x3ff0699ad8db4c8b, 0xbfead5c4a4b40f1a, 0xbfe7977f31b5fc6d,
           0x3fe2ff5484485472, 0xbfd96943f57e3046, 0xbfe04ecd797a151a,
           0x3fe360036da34794);
};

// Simple random test with similar values (vector-scalar)
void TEST_CASE3(void) {
  VSET(16, e16, m1);
  double dscalar_16;
  //                              0.1300
  BOX_HALF_IN_DOUBLE(dscalar_16, 0x3029);
  //              -0.2844,  0.4070, -0.1837, -0.2321, -0.5283, -0.6104, -0.7183,
  //              -0.1191,  0.7998,  0.1169,  0.1169, -0.9214, -0.4360, -0.6250,
  //              -0.5386,  0.6543
  VLOAD_16(v2, 0xb48d, 0x3683, 0xb1e1, 0xb36d, 0xb83a, 0xb8e2, 0xb9bf, 0xaf9f,
           0x3a66, 0x2f7c, 0x2f7c, 0xbb5f, 0xb6fa, 0xb900, 0xb84f, 0x393c);
  //               0.9268, -0.3337, -0.3225, -0.8306, -0.1857, -0.6831,  0.0557,
  //               0.5586,  0.2352,  0.6294,  0.6294, -0.8877, -0.2426,  0.5488,
  //               0.4001,  0.1772
  VLOAD_16(v1, 0x3b6a, 0xb557, 0xb529, 0xbaa5, 0xb1f1, 0xb977, 0x2b21, 0x3878,
           0x3387, 0x3909, 0x3909, 0xbb1a, 0xb3c3, 0x3864, 0x3667, 0x31ac);
  asm volatile("vfnmacc.vf v1, %[A], v2" ::[A] "f"(dscalar_16));
  //              -0.8896,  0.2808,  0.3464,  0.8608,  0.2544,  0.7627,  0.0377,
  //              -0.5430, -0.3394, -0.6445, -0.6445,  1.0078,  0.2993, -0.4675,
  //              -0.3301, -0.2622
  VCMP_U16(7, v1, 0xbb1e, 0x347e, 0x358b, 0x3ae3, 0x3412, 0x3a1a, 0x28d3,
           0xb858, 0xb56d, 0xb928, 0xb928, 0x3c08, 0x34ca, 0xb77b, 0xb548,
           0xb432);

  VSET(16, e32, m1);
  double dscalar_32;
  //                              -0.26917368
  BOX_FLOAT_IN_DOUBLE(dscalar_32, 0xbe89d122);
  //              -0.27745819, -0.86308837, -0.16746511, -0.68674469,
  //              -0.49064314, -0.74352056, -0.17169137,  0.26071417,
  //              0.71857828,  0.07920383, -0.43244356, -0.58339220, 0.80679923,
  //              0.23900302,  0.73513943, -0.80685192
  VLOAD_32(v2, 0xbe8e0f00, 0xbf5cf35c, 0xbe2b7bf9, 0xbf2fce80, 0xbefb3594,
           0xbf3e575d, 0xbe2fcfdd, 0x3e857c54, 0x3f37f4bf, 0x3da2359e,
           0xbedd693e, 0xbf155931, 0x3f4e8a65, 0x3e74bd35, 0x3f3c3219,
           0xbf4e8dd9);
  //               0.13509545, -0.29169917,  0.80494332, -0.63637137,
  //               0.63772237, -0.87242430, -0.44194883, -0.41286576,
  //               -0.57735479,  0.61664599,  0.94073379, -0.89744234,
  //               -0.70681161,  0.23247144,  0.06774496, -0.38581881
  VLOAD_32(v1, 0x3e0a5676, 0xbe955998, 0x3f4e10c4, 0xbf22e93c, 0x3f2341c6,
           0xbf5f5733, 0xbee2471e, 0xbed36324, 0xbf13cd86, 0x3f1ddc83,
           0x3f70d3ee, 0xbf65bec8, 0xbf34f19b, 0x3e6e0cfe, 0x3d8abdde,
           0xbec58a0b);
  asm volatile("vfnmacc.vf v1, %[A], v2" ::[A] "f"(dscalar_32));
  //              -0.20977989,  0.05937849, -0.85002053,  0.45151776,
  //              -0.76979059,  0.67228812,  0.39573404,  0.48304313,
  //              0.77077717, -0.59532642, -1.05713618,  0.74040854, 0.92398071,
  //              -0.16813812,  0.13013524,  0.16863550
  VCMP_U32(8, v1, 0xbe56d08a, 0x3d7336de, 0xbf599af2, 0x3ee72d57, 0xbf4510ff,
           0x3f2c1b13, 0x3eca9da7, 0x3ef7516f, 0x3f4551a7, 0xbf186750,
           0xbf87503d, 0x3f3d8b6a, 0x3f6c8a00, 0xbe2c2c66, 0x3e05422c,
           0x3e2caec9);

  VSET(16, e64, m1);
  double dscalar_64;
  //                                0.1021836258281641
  BOX_DOUBLE_IN_DOUBLE(dscalar_64, 0x3fba28b4c31e60e0);
  //                0.3274079371230154,  0.9254873656544997, 0.9683609308176633,
  //                -0.6778040243955326,  0.9669615854915627,
  //                0.8026267269428324, -0.7388821308618641, 0.7432413708598076,
  //                0.9355143976513562, -0.4219868517017851, 0.8950700270161456,
  //                0.6727820676214205, -0.8833440526985297, 0.0357808590148252,
  //                -0.3802125831332157,  0.9831607630398518
  VLOAD_64(v2, 0x3fd4f4406b993a2c, 0x3fed9d97ae0b1cd6, 0x3feefcd01012c05e,
           0xbfe5b09210bc082e, 0x3feef1596c459614, 0x3fe9af1e3ee3adfa,
           0xbfe7a4ec2374d0e2, 0x3fe7c8a2209c110c, 0x3fedefbbe3db30dc,
           0xbfdb01d523d9acc0, 0x3feca469e5b540fa, 0x3fe5876e42389dca,
           0xbfec445abf2e99e4, 0x3fa251de66953a60, 0xbfd8556728856e10,
           0x3fef760d8f7eee22);
  //                0.1671854121593166,  0.6264287337062140, 0.1587305627009998,
  //                -0.3348358495277817,  0.4721131630506652,
  //                0.2878076790245236,  0.5083797506594245, 0.9444607965181537,
  //                -0.2805814092841707, -0.7218856627753110,
  //                -0.3443302881655670,  0.3680926220616383,
  //                -0.2344410843781140,  0.3553553454507421,
  //                0.0951222110617760, -0.8329780449088213
  VLOAD_64(v1, 0x3fc56654e2cbd888, 0x3fe40bb445915f4a, 0x3fc4514877d696a0,
           0xbfd56df357d00344, 0x3fde371a20d41408, 0x3fd26b70e63cabf0,
           0x3fe044a59c60fcd4, 0x3fee3905d92cc95e, 0xbfd1f50bba2f6e40,
           0xbfe719aff62247a4, 0xbfd60981e7ac601c, 0x3fd78ed45b69d4fc,
           0xbfce022a5b1f1348, 0x3fd6be2458cadcb0, 0x3fb859ede1a22f80,
           0xbfeaa7c192a56bc8);
  asm volatile("vfnmacc.vf v1, %[A], v2" ::[A] "f"(dscalar_64));
  //              -0.2006411422994659, -0.7209983883869466, -0.2576811937222847,
  //              0.4040963223414386, -0.5709208038927434, -0.3698229881701340,
  //              -0.4328780954683192, -1.0204078946581041,  0.1849871561177042,
  //              0.7650058093340112,  0.2528687874349445, -0.4368399331233641,
  //              0.3247043825365946, -0.3590115633601233, -0.0562707107317317,
  //              0.7325151133694248
  VCMP_U64(9, v1, 0xbfc9ae9be43442c9, 0xbfe7126b3652e68a, 0xbfd07dd942f53687,
           0x3fd9dcb6d238fb8a, 0xbfe244fbb4aa695e, 0xbfd7ab2e09dffb6d,
           0xbfdbb44653cc3c92, 0xbff053973a823036, 0x3fc7ada8bcda50a5,
           0x3fe87aed768addeb, 0x3fd02f00910d95b4, 0xbfdbf52f7a9681dc,
           0x3fd4c7f4e3f733f9, 0xbfd6fa0ba2e11fba, 0xbfaccf83bca18481,
           0x3fe770c388f7eacc);
};

// Simple random test with similar values (vector-scalar) (masked)
void TEST_CASE4(void) {
  VSET(16, e16, m1);
  double dscalar_16;
  //                              0.1300
  BOX_HALF_IN_DOUBLE(dscalar_16, 0x3029);
  //               -0.2844,  0.4070, -0.1837, -0.2321, -0.5283, -0.6104,
  //               -0.7183, -0.1191,  0.7998,  0.1169,  0.2551, -0.9214,
  //               -0.4360, -0.6250, -0.5386,  0.6543
  VLOAD_16(v2, 0xb48d, 0x3683, 0xb1e1, 0xb36d, 0xb83a, 0xb8e2, 0xb9bf, 0xaf9f,
           0x3a66, 0x2f7c, 0x3415, 0xbb5f, 0xb6fa, 0xb900, 0xb84f, 0x393c);
  VLOAD_8(v0, 0xAA, 0xAA);
  //                0.9268, -0.3337, -0.3225, -0.8306, -0.1857, -0.6831, 0.0557,
  //                0.5586,  0.2352,  0.6294, -0.0325, -0.8877, -0.2426, 0.5488,
  //                0.4001,  0.1772
  VLOAD_16(v1, 0x3b6a, 0xb557, 0xb529, 0xbaa5, 0xb1f1, 0xb977, 0x2b21, 0x3878,
           0x3387, 0x3909, 0xa828, 0xbb1a, 0xb3c3, 0x3864, 0x3667, 0x31ac);
  asm volatile("vfnmacc.vf v1, %[A], v2, v0.t" ::[A] "f"(dscalar_16));
  //                0.0000,  0.2808,  0.0000,  0.8608,  0.0000,  0.7627, 0.0000,
  //                -0.5430,  0.0000, -0.6445,  0.0000,  1.0078,  0.0000,
  //                -0.4675,  0.0000, -0.2622
  VCMP_U16(10, v1, 0x3b6a, 0x347e, 0xb529, 0x3ae3, 0xb1f1, 0x3a1a, 0x2b21,
           0xb858, 0x3387, 0xb928, 0xa828, 0x3c08, 0xb3c3, 0xb77b, 0x3667,
           0xb432);

  VSET(16, e32, m1);
  double dscalar_32;
  //                              -0.26917368
  BOX_FLOAT_IN_DOUBLE(dscalar_32, 0xbe89d122);
  //               -0.27745819, -0.86308837, -0.16746511, -0.68674469,
  //               -0.49064314, -0.74352056, -0.17169137,  0.26071417,
  //               0.71857828,  0.07920383, -0.43244356, -0.58339220,
  //               0.80679923,  0.23900302,  0.73513943, -0.80685192
  VLOAD_32(v2, 0xbe8e0f00, 0xbf5cf35c, 0xbe2b7bf9, 0xbf2fce80, 0xbefb3594,
           0xbf3e575d, 0xbe2fcfdd, 0x3e857c54, 0x3f37f4bf, 0x3da2359e,
           0xbedd693e, 0xbf155931, 0x3f4e8a65, 0x3e74bd35, 0x3f3c3219,
           0xbf4e8dd9);
  VLOAD_8(v0, 0xAA, 0xAA);
  //                0.13509545, -0.29169917,  0.80494332, -0.63637137,
  //                0.63772237, -0.87242430, -0.44194883, -0.41286576,
  //                -0.57735479,  0.61664599,  0.94073379, -0.89744234,
  //                -0.70681161,  0.23247144,  0.06774496, -0.38581881
  VLOAD_32(v1, 0x3e0a5676, 0xbe955998, 0x3f4e10c4, 0xbf22e93c, 0x3f2341c6,
           0xbf5f5733, 0xbee2471e, 0xbed36324, 0xbf13cd86, 0x3f1ddc83,
           0x3f70d3ee, 0xbf65bec8, 0xbf34f19b, 0x3e6e0cfe, 0x3d8abdde,
           0xbec58a0b);
  asm volatile("vfnmacc.vf v1, %[A], v2, v0.t" ::[A] "f"(dscalar_32));
  //                0.00000000,  0.05937849,  0.00000000,  0.45151776,
  //                0.00000000,  0.67228812,  0.00000000,  0.48304313,
  //                0.00000000, -0.59532642,  0.00000000,  0.74040854,
  //                0.00000000, -0.16813812,  0.00000000,  0.16863550
  VCMP_U32(11, v1, 0x3e0a5676, 0x3d7336de, 0x3f4e10c4, 0x3ee72d57, 0x3f2341c6,
           0x3f2c1b13, 0xbee2471e, 0x3ef7516f, 0xbf13cd86, 0xbf186750,
           0x3f70d3ee, 0x3f3d8b6a, 0xbf34f19b, 0xbe2c2c66, 0x3d8abdde,
           0x3e2caec9);

  VSET(16, e64, m1);
  double dscalar_64;
  //                                0.1021836258281641
  BOX_DOUBLE_IN_DOUBLE(dscalar_64, 0x3fba28b4c31e60e0);
  //                 0.3274079371230154,  0.9254873656544997,
  //                 0.9683609308176633, -0.6778040243955326,
  //                 0.9669615854915627,  0.8026267269428324,
  //                 -0.7388821308618641,  0.7432413708598076,
  //                 0.9355143976513562, -0.4219868517017851,
  //                 0.8950700270161456,  0.6727820676214205,
  //                 -0.8833440526985297,  0.0357808590148252,
  //                 -0.3802125831332157,  0.9831607630398518
  VLOAD_64(v2, 0x3fd4f4406b993a2c, 0x3fed9d97ae0b1cd6, 0x3feefcd01012c05e,
           0xbfe5b09210bc082e, 0x3feef1596c459614, 0x3fe9af1e3ee3adfa,
           0xbfe7a4ec2374d0e2, 0x3fe7c8a2209c110c, 0x3fedefbbe3db30dc,
           0xbfdb01d523d9acc0, 0x3feca469e5b540fa, 0x3fe5876e42389dca,
           0xbfec445abf2e99e4, 0x3fa251de66953a60, 0xbfd8556728856e10,
           0x3fef760d8f7eee22);
  VLOAD_8(v0, 0xAA, 0xAA);
  //                 0.1671854121593166,  0.6264287337062140,
  //                 0.1587305627009998, -0.3348358495277817,
  //                 0.4721131630506652,  0.2878076790245236,
  //                 0.5083797506594245,  0.9444607965181537,
  //                 -0.2805814092841707, -0.7218856627753110,
  //                 -0.3443302881655670,  0.3680926220616383,
  //                 -0.2344410843781140,  0.3553553454507421,
  //                 0.0951222110617760, -0.8329780449088213
  VLOAD_64(v1, 0x3fc56654e2cbd888, 0x3fe40bb445915f4a, 0x3fc4514877d696a0,
           0xbfd56df357d00344, 0x3fde371a20d41408, 0x3fd26b70e63cabf0,
           0x3fe044a59c60fcd4, 0x3fee3905d92cc95e, 0xbfd1f50bba2f6e40,
           0xbfe719aff62247a4, 0xbfd60981e7ac601c, 0x3fd78ed45b69d4fc,
           0xbfce022a5b1f1348, 0x3fd6be2458cadcb0, 0x3fb859ede1a22f80,
           0xbfeaa7c192a56bc8);
  asm volatile("vfnmacc.vf v1, %[A], v2, v0.t" ::[A] "f"(dscalar_64));
  //                -0.2006411422994659, -0.7209983883869466,
  //                -0.2576811937222847,  0.4040963223414386,
  //                -0.5709208038927434, -0.3698229881701340,
  //                -0.4328780954683192, -1.0204078946581041,
  //                0.1849871561177042,  0.7650058093340112, 0.2528687874349445,
  //                -0.4368399331233641,  0.3247043825365946,
  //                -0.3590115633601233, -0.0562707107317317, 0.7325151133694248
  VCMP_U64(12, v1, 0x3fc56654e2cbd888, 0xbfe7126b3652e68a, 0x3fc4514877d696a0,
           0x3fd9dcb6d238fb8a, 0x3fde371a20d41408, 0xbfd7ab2e09dffb6d,
           0x3fe044a59c60fcd4, 0xbff053973a823036, 0xbfd1f50bba2f6e40,
           0x3fe87aed768addeb, 0xbfd60981e7ac601c, 0xbfdbf52f7a9681dc,
           0xbfce022a5b1f1348, 0xbfd6fa0ba2e11fba, 0x3fb859ede1a22f80,
           0x3fe770c388f7eacc);
};

int main(void) {
  enable_vec();
  enable_fp();

  TEST_CASE1();
  TEST_CASE2();
  TEST_CASE3();
  TEST_CASE4();

  EXIT_CHECK();
}
